use actix_web::{get, web, HttpResponse, Responder, Scope};
use serde::Deserialize;

use crate::models::{ApiResponse, StockPrice};
use crate::services::price_service::PriceService;

#[derive(Deserialize)]
pub struct SearchQuery {
    pub q: String,
}

#[get("/api/stocks/search")]
async fn search(query: web::Query<SearchQuery>) -> impl Responder {
    // 简化：返回模拟的匹配
    let q = query.q.to_uppercase();
    let data = vec![
        ("AAPL", "Apple Inc."),
        ("MSFT", "Microsoft Corporation"),
        ("GOOG", "Alphabet Inc."),
        ("TSLA", "Tesla, Inc."),
    ]
    .iter()
    .filter(|(s, _)| s.contains(&q))
    .map(|(s, n)| serde_json::json!({ "symbol": s, "name": n }))
    .collect::<Vec<_>>();

    HttpResponse::Ok().json(ApiResponse { data })
}

#[get("/api/stocks/{symbol}/price")]
async fn price(
    path: web::Path<String>,
    svc: web::Data<PriceService>,
) -> impl Responder {
    let symbol = path.into_inner().to_uppercase();
    let p: StockPrice = svc.tick(&symbol);
    HttpResponse::Ok().json(ApiResponse { data: p })
}

#[derive(Deserialize)]
pub struct HistoryQuery {
    pub minutes: Option<i64>,
}

#[get("/api/stocks/{symbol}/history")]
async fn history(
    path: web::Path<String>,
    svc: web::Data<PriceService>,
    query: web::Query<HistoryQuery>,
) -> impl Responder {
    let symbol = path.into_inner().to_uppercase();
    let minutes = query.minutes.unwrap_or(60);
    let data = svc.history(&symbol, minutes);
    HttpResponse::Ok().json(ApiResponse { data })
}

pub fn stocks_scope() -> Scope {
    web::scope("")
        .service(search)
        .service(price)
        .service(history)
}